package com.hddz.comlib.packet;

import java.nio.ByteBuffer;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import android.util.Log;

import com.hddz.comlib.model.Sensor;
import com.hddz.comlib.util.ConvertUtility;

public class CommandPacket extends Packet {

	private int stationId;

	public int getStationId() {
		return stationId;
	}

	public void setStationId(int stationId) {
		this.stationId = stationId;
	}

	public String getCommandFlag() {
		return commandFlag;
	}

	public Map<String, Object> getnParams() {
		return nParams;
	}

	private final String TAG = "CommandPacket";
	private SimpleDateFormat dateformat = new SimpleDateFormat("yyMMdd HHmm");
	/**
	 * 命令标志
	 */
	private String commandFlag;
	/**
	 * 存储的键值对
	 */
	private Map<String, Object> nParams = new HashMap<String, Object>();

	@Override
	public String createViewText() {
		// TODO Auto-generated method stub
		StringBuilder sb = new StringBuilder();
		Iterator<Map.Entry<String, Object>> it = nParams.entrySet().iterator();
		while (it.hasNext()) {
			Map.Entry<String, Object> entry = it.next();
			sb.append(entry.getKey());
			sb.append(":");
			sb.append(entry.getValue());
			sb.append(";");
		}
		return sb.toString();
	}

	@Override
	public Boolean parse(ByteBuffer data, int len) {
		// TODO Auto-generated method stub
		byte[] b = new byte[len + 4];
		int index = 0;
		Log.d(TAG, "limit=" + data.limit() + " position=" + data.position());
		int perPosition = data.position();
		try {
			// this.sourceText = Utility.bystesToStr(data, start - 3, len + 5);
			data.position(perPosition - 3);
			data.get(b, 0, len + 4);
			this.sourceText = ConvertUtility.bystesToStr(b, 0, len + 4);
			Log.d(TAG, this.sourceText);
			data.position(perPosition);
			String[] sencondParts = null;
			if (len > 0) {
				if ((data.get() & 0xff) == 0x53 && (data.get() & 0xff) == 0x54)// 命令报文开头
				{
					data.position(data.position() - 2);// 回退下
					Log.d(TAG, "limit=" + data.limit() + " position=" + data.position());
					if (ConvertUtility.checkByteInByteBuffer(0x3A, data, len) && ConvertUtility.checkByteInByteBuffer(0x2e, data, len)
							&& ConvertUtility.checkByteInByteBuffer(0x3b, data, len)) // 检查是否有“:”号，如果有，则视为以字符串方式的标准协议，否则是另外新增的协议
					{
						// 标准协议
						String result = ConvertUtility.byteBufferToString(data, len);
						if (result.endsWith(".")) {
							result = result.substring(0, result.length() - 1);
						}
						String[] parts = result.split(";");
						stationId = Integer.parseInt(parts[index].split(":")[1]);
						index++;
						this.nParams.put("ST", stationId);
						sencondParts = parts[index].split(":");
						this.commandFlag = sencondParts[0];
						this.nParams.put(sencondParts[0], sencondParts[1]);
						index++;
						for (int i = index; i < parts.length; i++) {
							sencondParts = parts[i].split(":");

							if (sencondParts[0].equals("Restart")) {
								parts[i] = parts[i].substring(8);
								sencondParts = parts[i].split(",");
								if (sencondParts.length == 2) {
									Date lastRootdt = ConvertUtility.convertDateTime(sencondParts[0]);
									if (lastRootdt != null) {
										this.nParams.put("Restart", lastRootdt);
									}
									this.nParams.put("RestartTimes", sencondParts[1].trim());
								}
								continue;
							}

							if (sencondParts.length == 2) {
								this.nParams.put(sencondParts[0], sencondParts[1]);
							}
						}

						Log.d(TAG, "two1 limit=" + data.limit() + " position=" + data.position());
					} else {
						// 杨海峰为数据量太长修改的特殊协议
						data.position(data.position() + 2);
						stationId = ((data.get() & 0xff) * 256 + (data.get() & 0xff)) * 256 + (data.get() & 0xff);
						this.nParams.put("ST", stationId);
						int commonflag = data.get() & 0xff;
						if (commonflag == 0x4E || commonflag == 0x48 || commonflag == 0x53 || commonflag == 0x52) // 版本报文
						{
							this.commandFlag = "Y";
							do {
								switch (commonflag) {
								case 0x4E:// 设备型号
									this.nParams.put("N", (data.get() & 0xff));
									break;
								case 0x48:// 硬件设备号
									this.nParams.put("H", (data.get() & 0xff) + "." + (data.get() & 0xff));
									break;
								case 0x53:// 软件版本号
									this.nParams.put("S", (data.get() & 0xff) + "." + (data.get() & 0xff) + "." + (data.get() & 0xff) + (data.get() & 0xff));
									break;
								case 0x52:// 最后一次重启时间
									this.nParams.put(
											"R",
											dateformat.parse(String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))
													+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))
													+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff)) + " "
													+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))
													+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))));
									this.nParams.put("T", (data.get() & 0xff));
									break;
								}
								commonflag = data.get() & 0xff;
							} while (data.position() < perPosition + len);
							data.position(data.position() - 1);
						} else {// 实时数据
							data.position(data.position() - 1);
							Log.d(TAG, "two21 limit=" + data.limit() + " position=" + data.position());
							this.commandFlag = "Z";
							Date dt = new Date();
							try {
								dt = dateformat.parse(String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))
										+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))
										+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff)) + " "
										+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff))
										+ String.format("%02d", ConvertUtility.BCDToInt(data.get() & 0xff)));
							} catch (Exception e) {
							}
							Log.d(TAG, "two22 limit=" + data.limit() + " position=" + data.position());
							while (data.position() < perPosition + len - 2) {
								int no_flag = data.get() & 0xff;
								int no = no_flag % 16;
								int flag = no_flag / 16;
								try {
									switch (flag) {
									case 1:// 脉冲量 累计流量 P
										this.nParams.put("P" + no, (data.get() & 0xff) * 1000000 + (data.get() & 0xff) * 10000 + (data.get() & 0xff) * 100
												+ (data.get() & 0xff));
										break;
									case 3:// 模拟量 A
										this.nParams.put("A" + no, ((data.get() & 0xff) * 256 + (data.get() & 0xff)) / 1000.0);
										break;
									}
								} catch (Exception ex) {
									// Debug.WriteLine(ex.Message);
								}
							}
							this.nParams.put("V", ((data.get() & 0xff) * 2) / 100.0);
						}

						Log.d(TAG, "two2 limit=" + data.limit() + " position=" + data.position());
					}
				}
			}
			this.viewText = this.createViewText();
			Log.d(TAG, this.viewText);
			return true;
		} catch (Exception e) {
			return false;
		}
	}

	public List<Sensor> getSensors() {
		List<Sensor> sensors = new ArrayList<Sensor>();
		for (Map.Entry<String, Object> entry : nParams.entrySet()) {
			if (entry.getKey().startsWith("P") || entry.getKey().startsWith("A") || entry.getKey().startsWith("V")) {
				Sensor sensor = new Sensor();
				sensor.setChannel(entry.getKey());
				sensor.setValue((Double) entry.getValue());
				sensors.add(sensor);
			}
		}
		return sensors;
	}

	@Override
	public Boolean parse(List<Byte> data, int start, int len) {
		// TODO Auto-generated method stub
		return null;
	}
}
